<?php


namespace app\live\service;


use app\aliyun\controller\AliyunRtc;
use app\chat\LiveMessage;
use app\common\cachemodel\live\LiveAnchorInfo;
use app\common\cachemodel\live\LiveRecordingInfo;
use app\common\cachemodel\live\LiveRtcRecord;
use think\Cache;
use think\Log;

class Rtc
{
    /**
     * rtc 用户进入 连麦成功
     * @param int $liveId
     * @param int $uid
     * @throws \Exception
     */
    public function rtcUserJoin(int $liveId, int $uid)
    {
        $liveRecordId = (new LiveRecordingInfo())->getNewestRecord($liveId);
        $rtcRecordModel = new LiveRtcRecord();
        $nowRtcData = $rtcRecordModel->getNowRtcDataByCache($liveRecordId);
        if ($nowRtcData && (int)$nowRtcData['uid'] === $uid && $nowRtcData['status'] > 1)
        {
            $nowRtcData['status'] = (int)$nowRtcData['status']; // 当前连麦状态 1=>邀请等待用户接受 2=>用户接受开始连麦中 3=>连麦成功 连麦中

            if ($nowRtcData['status'] === 2)
            { // 用户接受开始连麦中
                $nowRtcData['status'] = 3;
                $rtcRecordModel->saveNowRtcDataToCache($liveRecordId, $nowRtcData);
                // 拼接 发送给所有用户 数据
                $popMsgRtc2All = [
                    'type' => 1,
                    'toast' => '',
                    'user_info' => [
                        'name' => $nowRtcData['nickname'],
                        'avatar' => $nowRtcData['avatar'],
                        'uen' => $nowRtcData['uen'],
                        'status' => 1,
                        'des_network' => '',
                    ],
                    'btn_list' => []
                ];
                $liveInfo = (new LiveAnchorInfo())->getInfoById($nowRtcData['live_id'], ['name', 'avatar']);

                // 拼接 发送给 连麦用户 数据
                $popMsgRtc2RtcUser = [
                    'type' => 1,
                    'toast' => '',
                    'user_info' => [
                        'name' => $liveInfo['name'],
                        'avatar' => $liveInfo['avatar'],
                        'uen' => $nowRtcData['uen'],
                        'status' => 1,
                        'des_network' => '',
                    ],
                    'btn_list' => [
                        [
                            'type' => 1,
                            'title' => '挂断',
                            'target' => 'api',
                            'link' => '/api/v29/rtc_interaction?action=3&live_record_id=' . $liveRecordId . '&need_auth=2',
                            'mic_auth_deny' => null,
                            'action' => 2,
                        ]
                    ]
                ];
                // 拼接 发送给管理端 数据
                $popMsgRtc2Admin = [
                    'type' => 1,
                    'toast' => '',
                    'user_info' => [
                        'name' => $nowRtcData['nickname'],
                        'avatar' => $nowRtcData['avatar'],
                        'uen' => $nowRtcData['uen'],
                        'status' => 1,
                        'des_network' => '',
                    ],
                    'btn_list' => [
                        [
                            'type' => 1,
                            'title' => '挂断',
                            'target' => 'api',
                            'link' => '/live/v2/live/request_rtc_interaction?action=5&need_auth=2',
                            'mic_auth_deny' => null,
                            'action' => 2,
                        ]
                    ]
                ];

                $userClientId = LiveMessage::getClientIdByUid($uid);
                // 向直播间所有人 发送消息
                LiveMessage::sendMsg(LiveMessage::who(LiveMessage::WHO_TYPE_APP_USER, $liveId, $liveId)
                    , LiveMessage::MSG_TYPE_POP_MSG_RTC, $popMsgRtc2All, $userClientId);
                // 向连麦用户发送消息
                LiveMessage::sendMsg(LiveMessage::who(LiveMessage::WHO_TYPE_UID, $liveId, (string)$uid)
                    , LiveMessage::MSG_TYPE_POP_MSG_RTC, $popMsgRtc2RtcUser);
                // 向管理员 发送消息
                LiveMessage::sendMsg(LiveMessage::who(LiveMessage::WHO_TYPE_LIVER, $liveId, $liveId)
                    , LiveMessage::MSG_TYPE_POP_MSG_RTC, $popMsgRtc2Admin);

                // 向连麦用户发送消息
                LiveMessage::sendMsg(LiveMessage::who(LiveMessage::WHO_TYPE_UID, $liveId, (string)$nowRtcData['uid'])
                    , LiveMessage::MSG_TYPE_RTC_STATUS, 2);
                // 向管理员 发送消息
                LiveMessage::sendMsg(LiveMessage::who(LiveMessage::WHO_TYPE_LIVER, $liveId, $liveId)
                    , LiveMessage::MSG_TYPE_RTC_STATUS, 2);
            }
        } else
        {   // 当前没有连麦信息
            // 自动踢出
            $result = (new AliyunRtc())->removeTerminals($liveId, [$uid]);
            //[
            //      'code' => 200,
            //      'msg' => '请求成功!',
            //      'data' =>[
            //           'result' =>[
            //              'RequestId' => '9695BD39-96CC-5E25-812C-DA83E60297C7',
            //              'Terminals' =>[
            //                  'Terminal' => [
            //                         0 =>[
            //                                  'Message' => 'ok',
            //                                  'Id' => '12346392',
            //                                   'Code' => 0,
            //                                ],
            //                  ],
            //              ],
            //          ],
            //      ],
            // ];
            if ($result['code'] === 200 && isset($result['data']['result']['Terminals']['Terminal']) && !empty($result['data']['result']['Terminals']['Terminal']))
            {
                Log::write("连麦回调：用户非法进入连麦，执行踢出操作--成功--；liveId:【{$liveId}】uid：【{$uid}】;踢出结果:" . json_encode($result), 'log');
            } else
            {
                Log::write("连麦回调：用户非法进入连麦，执行踢出操作--失败--；liveId:【{$liveId}】uid：【{$uid}】;踢出结果:" . json_encode($result), 'error');
            }
        }
    }

    /**
     * 用户离会  连麦断开
     * @param $liveId
     * @param $role int  1=>主播   2=>观众
     * @param $id
     * @throws \Exception
     */
    public function rtcClose($liveId, int $role, $id)
    {
        $liveRecordId = (new LiveRecordingInfo())->getNewestRecord($liveId);
        $rtcRecordModel = new LiveRtcRecord();
        $nowRtcData = $rtcRecordModel->getNowRtcDataByCache($liveRecordId);
        $time = time();
        if ($nowRtcData)
        {   // 当前直播有连麦信息
            if ($role === 1)
            {   // 主播离会 连麦中断
                if ($nowRtcData['id'] > 0)
                {
                    $questionRtcInfo = $rtcRecordModel->getInfoById($nowRtcData['id']);
                    // 计算连麦时长
                    $duration = $time - $questionRtcInfo['start_time'];
                    $status = (int)$nowRtcData['status'] === 1 ? 16 : 17;
                    // 更新连麦记录
                    $rtcRecordModel->updateRtcInfo((int)$nowRtcData['id'], [
                        'status' => $status, // 用户断开连麦
                        'duration' => $status === 16 ? 0 : $duration,
                        'cancel' => $time,
                        'update_time' => $time
                    ]);
                }
                // 列表连麦信息删除
                if ((int)$nowRtcData['type'] === 1)
                {
                    $rtcRecordModel->rtcListDel($liveRecordId, (int)$nowRtcData['uid']);    // 删除从列表中移除
                }
                $rtcRecordModel->delNowRtcDataByCache($liveRecordId); // 删除当前连麦信息
                // 拼接 发送给所有用户 数据
                $popMsgRtc2All = [
                    'type' => 0,
                    'toast' => '',
                    'user_info' => null,
                    'btn_list' => []
                ];

                // 拼接 发送给 连麦用户 数据
                $popMsgRtc2RtcUser = [
                    'type' => 2,
                    'toast' => '主播连接断开',
                    'user_info' => null,
                    'btn_list' => []
                ];

                // 拼接 发送给管理端 数据
                $popMsgRtc2Admin = [
                    'type' => 2,
                    'toast' => '主播连接断开',
                    'user_info' => null,
                    'btn_list' => []
                ];

                $userClientId = LiveMessage::getClientIdByUid($nowRtcData['uid']);
                // 向直播间所有人 发送消息
                LiveMessage::sendMsg(LiveMessage::who(LiveMessage::WHO_TYPE_APP_USER, $liveId, $liveId)
                    , LiveMessage::MSG_TYPE_POP_MSG_RTC, $popMsgRtc2All, $userClientId);
                // 向连麦用户发送消息
                LiveMessage::sendMsg(LiveMessage::who(LiveMessage::WHO_TYPE_UID, $liveId, (string)$nowRtcData['uid'])
                    , LiveMessage::MSG_TYPE_POP_MSG_RTC, $popMsgRtc2RtcUser);
                // 向管理员 发送消息
                LiveMessage::sendMsg(LiveMessage::who(LiveMessage::WHO_TYPE_LIVER, $liveId, $liveId)
                    , LiveMessage::MSG_TYPE_POP_MSG_RTC, $popMsgRtc2Admin);

                // 获取当前 rtc 开启状态
                $rtcSwitch = (int)(Cache::get("live:rtc_switch:{$liveId}:{$liveRecordId}", 0));
                $allRequestRtcUserList = $rtcRecordModel->getRtcUserList($liveRecordId);
                if ($allRequestRtcUserList)
                {
                    $adminRtcStatus = 3;
                } else
                {
                    $adminRtcStatus = $rtcSwitch;
                }

                // 向连麦用户发送消息
                LiveMessage::sendMsg(LiveMessage::who(LiveMessage::WHO_TYPE_UID, $liveId, (string)$nowRtcData['uid'])
                    , LiveMessage::MSG_TYPE_RTC_STATUS, $rtcSwitch);
                // 向直播间 管理员和主播 发送连麦 状态消息
                LiveMessage::sendMsg(LiveMessage::who(LiveMessage::WHO_TYPE_LIVER, $liveId, $liveId)
                    , LiveMessage::MSG_TYPE_RTC_STATUS, $adminRtcStatus);
            } else
            {   // 用户离会
                if ((int)$nowRtcData['uid'] === $id)
                {   // 连麦用户离会   连麦中断
                    if ($nowRtcData['id'] > 0)
                    {
                        $questionRtcInfo = $rtcRecordModel->getInfoById($nowRtcData['id']);
                        // 计算连麦时长
                        $duration = $time - $questionRtcInfo['start_time'];
                        // 更新连麦记录
                        $rtcRecordModel->updateRtcInfo((int)$nowRtcData['id'], [
                            'status' => 18, // 用户断开连麦
                            'duration' => $duration,
                            'cancel' => $time,
                            'update_time' => $time
                        ]);
                    }
                    // 列表连麦信息删除
                    if ((int)$nowRtcData['type'] === 1)
                    {
                        $rtcRecordModel->rtcListDel($liveRecordId, (int)$nowRtcData['uid']);    // 删除从列表中移除
                    }
                    $rtcRecordModel->delNowRtcDataByCache($liveRecordId); // 删除当前连麦信息
                    // 拼接 发送给所有用户 数据
                    $popMsgRtc2All = [
                        'type' => 0,
                        'toast' => '',
                        'user_info' => null,
                        'btn_list' => []
                    ];

                    // 拼接 发送给 连麦用户 数据
                    $popMsgRtc2RtcUser = [
                        'type' => 2,
                        'toast' => '服务连接断开',
                        'user_info' => null,
                        'btn_list' => []
                    ];

                    // 拼接 发送给管理端 数据
                    $popMsgRtc2Admin = [
                        'type' => 2,
                        'toast' => '用户连接断开',
                        'user_info' => null,
                        'btn_list' => []
                    ];
                    $userClientId = LiveMessage::getClientIdByUid($nowRtcData['uid']);
                    // 向直播间所有人 发送消息
                    LiveMessage::sendMsg(LiveMessage::who(LiveMessage::WHO_TYPE_APP_USER, $liveId, $liveId)
                        , LiveMessage::MSG_TYPE_POP_MSG_RTC, $popMsgRtc2All, $userClientId);
                    // 向连麦用户发送消息
                    LiveMessage::sendMsg(LiveMessage::who(LiveMessage::WHO_TYPE_UID, $liveId, (string)$nowRtcData['uid'])
                        , LiveMessage::MSG_TYPE_POP_MSG_RTC, $popMsgRtc2RtcUser);
                    // 向管理员 发送消息
                    LiveMessage::sendMsg(LiveMessage::who(LiveMessage::WHO_TYPE_LIVER, $liveId, $liveId)
                        , LiveMessage::MSG_TYPE_POP_MSG_RTC, $popMsgRtc2Admin);

                    // 获取当前 rtc 开启状态
                    $rtcSwitch = (int)(Cache::get("live:rtc_switch:{$liveId}:{$liveRecordId}", 0));
                    $allRequestRtcUserList = $rtcRecordModel->getRtcUserList($liveRecordId);
                    if ($allRequestRtcUserList)
                    {
                        $adminRtcStatus = 3;
                    } else
                    {
                        $adminRtcStatus = $rtcSwitch;
                    }

                    // 向连麦用户发送消息
                    LiveMessage::sendMsg(LiveMessage::who(LiveMessage::WHO_TYPE_UID, $liveId, (string)$nowRtcData['uid'])
                        , LiveMessage::MSG_TYPE_RTC_STATUS, $rtcSwitch);
                    // 向直播间 管理员和主播 发送连麦 状态消息
                    LiveMessage::sendMsg(LiveMessage::who(LiveMessage::WHO_TYPE_LIVER, $liveId, $liveId)
                        , LiveMessage::MSG_TYPE_RTC_STATUS, $adminRtcStatus);
                }
            }
        }
    }
}
